local desc_nian_capturing = [[
  # 模式介绍

  游戏人数4~6人

  2人扮演人类，1人扮演年兽，其余扮演生肖兽。人类将与年兽、生肖兽展开对抗！
  
  ---
  
  ## 生肖兽专属技能

  **福禄：** 锁定技，游戏开始时，你摸两张牌；你的摸牌阶段摸牌数+2。
  
  ---

  ## 人类专属技能

  **捕捉：** 出牌阶段限一次，你可以指定一名生肖兽，进行捕捉。有[100-12X]%的概率捕捉成功（X为其体力值）。成功则其死亡，你失去上次以此法获得的技能，然后获得其生肖技能。

  **爆竹：** 限定技，出牌阶段，你可以令所有角色各失去1点体力和所有护甲，得到以下效果直到你的下个回合开始：使用的【杀】造成的伤害+1。

  **烟花：** 限定技，出牌阶段，你可以指定一名其他角色，其得到以下效果直到你的下个回合开始：造成或受到伤害时，进行一次判定，若结果为红色，防止此伤害。
  
  ---

]]

local nian_capturing_getLogic = function()
  local nian_capturing_logic = GameLogic:subclass("nian_capturing_logic")

  function nian_capturing_logic:initialize(room)
    GameLogic.initialize(self, room)
    self.role_table = {nil, nil, nil,
    {"rebel", "rebel", "lord" , "loyalist"},
    {"rebel", "rebel", "lord" , "loyalist", "loyalist"},
    {"rebel", "rebel", "lord" , "loyalist", "loyalist", "loyalist"},
  }
  end

  function nian_capturing_logic:assignRoles()
    local room = self.room
    local players = room.players
    local n = #players
    local roles = table.simpleClone(self.role_table[n])
    for _, player in ipairs(players) do
      if player.id > 0 then
        player.role = table.remove(roles, 1)
      else
        player.role = table.remove(roles, #roles)
      end
      room:broadcastProperty(player, "role")
    end
  end

  function nian_capturing_logic:chooseGenerals()
    local room = self.room
    local zodiac_list = {
      "zodiac__shu", "zodiac__niu", "zodiac__hu", "zodiac__tu",
      "zodiac__long", "zodiac__she", "zodiac__ma", "zodiac__yang",
      "zodiac__hou", "zodiac__ji", "zodiac__gou", "zodiac__zhu"
    }
    local generalNum = room.settings.generalNum
    local lord = room:getLord()
    local num = 1
    while not room.current do
      if room.players[num].role == "rebel" then
        room.current = room.players[num]
        break
      end
      num = num + 1
    end
    room:doBroadcastNotify("ShowToast", Fk:translate("nian_intro"))
    --年兽来啦！
    if lord ~= nil then
      room:setPlayerGeneral(lord, "nian__Nian", true)
      room:askForChooseKingdom({lord})
      room:broadcastProperty(lord, "general")
      room:broadcastProperty(lord, "kingdom")
    end
    --余下选将
    local humen = table.random(room.general_pile, generalNum * 2)
    local zodiacs = table.simpleClone(zodiac_list)
    for _, p in ipairs(room:getOtherPlayers(lord, true)) do
      if p.role == "loyalist" then
        local arg = {}
        table.shuffle(zodiacs)
        for i = 1, 4 do
          table.insert(arg, table.remove(zodiacs, 1))
        end
        p.request_data = json.encode{ arg, 1 }
        p.default_reply = table.random(arg, 1)
      else
        local arg = {}
        table.shuffle(humen)
        for i = 1, generalNum do
          table.insert(arg, table.remove(humen, 1))
        end
        p.request_data = json.encode{ arg, 1 }
        p.default_reply = table.random(arg, 1)
      end
    end
    
    room:notifyMoveFocus(room:getOtherPlayers(lord, true), "AskForGeneral")
    room:doBroadcastRequest("AskForGeneral", room:getOtherPlayers(lord, true))

    for _, p in ipairs(room:getOtherPlayers(lord, true)) do
      local genral
      if p.general == "" and p.reply_ready then
        local _generals = json.decode(p.client_reply)
        genral = _generals[1]
      else
        genral = p.default_reply[1]
      end
      room:setPlayerGeneral(p, genral, true, true)
      if table.contains(room.general_pile, genral) then
        table.removeOne(room.general_pile, genral)
      end
      p.default_reply = ""
    end

    room:askForChooseKingdom(room:getOtherPlayers(lord, true))
  end

  function nian_capturing_logic:broadcastGeneral()
    local room = self.room
    local players = room.players
    for _, p in ipairs(players) do
      assert(p.general ~= "")
      local general = Fk.generals[p.general]
      p.maxHp = p:getGeneralMaxHp()
      p.hp = general.hp
      p.shield = general.shield
      -- TODO: setup AI here
      room:broadcastProperty(p, "general")
      room:broadcastProperty(p, "kingdom")
      room:broadcastProperty(p, "maxHp")
      room:broadcastProperty(p, "hp")
      room:broadcastProperty(p, "shield")
    end
  end

  function nian_capturing_logic:attachSkillToPlayers()
    local room = self.room

    local addRoleModSkills = function(player, skillName)
      local skill = Fk.skills[skillName]
      if skill.lordSkill then
        return
      end
      if #skill.attachedKingdom > 0 and not table.contains(skill.attachedKingdom, player.kingdom) then
        return
      end
      room:handleAddLoseSkills(player, skillName, nil, false)
    end

    for _, p in ipairs(room.alive_players) do
      local skills = Fk.generals[p.general]:getSkillNameList()
      for _, sname in ipairs(skills) do
        addRoleModSkills(p, sname)
      end
      if p.role == "loyalist" then
        room:handleAddLoseSkills(p, "nian_fulu", nil, false)
      elseif p.role == "rebel" then
        room:handleAddLoseSkills(p, "nian_buzhuo|nian_baozhu|nian_yanhua", nil, false)
      end
    end
  end

  return nian_capturing_logic
end

local nian_capturing_rule = fk.CreateTriggerSkill{
  name = "#nian_capturing_rule",
  priority = 0.001,
  refresh_events = {fk.GameStart},
  can_refresh = function(self, event, target, player, data)
    return player.seat == 1
  end,
  on_refresh = function(self, event, target, player, data)
    local room = player.room
    room:setTag("SkipNormalDeathProcess", true)
    local players = {}
    local seat_list = { nil, nil, nil,
      {"rebel","rebel","lord","loyalist"},
      {"rebel","rebel","loyalist","lord","loyalist"},
      {"rebel","rebel","loyalist","loyalist","lord","loyalist"},
    }
    for s, p in pairs(room.players) do
      if p == players[1] then return end
      local i = 1
      while true do
        if p.role == seat_list[#room.players][i] and not players[i] then
          players[i] = p
          i = 1
          break
        end
        i = i + 1
      end
    end
    room.players = players
    local player_circle = {}
    for i = 1, #room.players do
      room.players[i].seat = i
      table.insert(player_circle, room.players[i].id)
    end
    for i = 1, #room.players - 1 do
      room.players[i].next = room.players[i + 1]
    end
    room.players[#room.players].next = room.players[1]
    room:doBroadcastNotify("ArrangeSeats", json.encode(player_circle))
    room:doBroadcastNotify("ShowToast", Fk:translate("nian_changeSeat_intro"))
  end,
}

local nian_capturing = fk.CreateGameMode{
  name = "nian_capturing",
  minPlayer = 4,
  maxPlayer = 6,
  rule = nian_capturing_rule,
  logic = nian_capturing_getLogic,
  surrender_func = function(self, playedTime)
    return Fk.game_modes["aaa_role_mode"].surrenderFunc(self, playedTime)
  end,
}

local fulu = fk.CreateTriggerSkill{
  name = "nian_fulu",
  anim_type = "drawcard",
  frequency = Skill.Compulsory,
  events = {fk.DrawNCards, fk.GameStart},
  can_trigger = function(self, event, target, player, data)
      return target == player and player:hasSkill(self)
    end,
  on_use = function(self, event, target, player, data)
    if event == fk.DrawNCards then
      data.n = data.n + 2
    else
      player.room:drawCards(player, 2, self.name)
    end
  end,
}
Fk:addSkill(fulu)

local buzhuo = fk.CreateActiveSkill{
  name = "nian_buzhuo",
  anim_type = "special",
  target_num = 1,
  can_use = function(self, player)
    return player:usedSkillTimes(self.name, Player.HistoryPhase) == 0
  end,
  card_filter = Util.FalseFunc,
  target_filter = function(self, to_select, selected, selected_cards)
    return #selected == 0 and to_select ~= Self.id and Fk:currentRoom():getPlayerById(to_select).role == "loyalist"
  end,
  on_use = function(self, room, effect)
    local player = room:getPlayerById(effect.from)
    local target = room:getPlayerById(effect.tos[1])
    local zodiac_skill = table.filter(target.player_skills, function(s) return s.name:startsWith("zodiac") end)
    if math.random() < 1 - player.hp * 0.12 then
      room:killPlayer({who = effect.tos[1]})
      for _, skill in pairs(player.player_skills) do
        if skill.name:startsWith("zodiac") then
          room:handleAddLoseSkills(player, "-"+skill.name)
        end
      end
      if #zodiac_skill == 0 then return end
      room:handleAddLoseSkills(player, zodiac_skill[1].name)
    end
  end,
}
Fk:addSkill(buzhuo)

local baozhu = fk.CreateActiveSkill{
  name = "nian_baozhu",
  anim_type = "special",
  frequency = Skill.Limited,
  can_use = function(self, player)
    return player:usedSkillTimes(self.name, Player.HistoryGame) == 0
  end,
  card_filter = Util.FalseFunc,
  target_filter = Util.FalseFunc,
  on_use = function(self, room, effect)
    Self.tag[self.name] = 1
    for _, p in ipairs(room:getAlivePlayers()) do
      if p.dead then return end
      room:setPlayerMark(p, "@@nian_baozhu", 1)
      if p.shield > 0 then room:changeShield(p, -p.shield) end
      room:loseHp(p, 1, self.name)
      room:delay(200)
    end
  end,
}
local baozhu_add = fk.CreateTriggerSkill{
  name = "#nian_baozhu_add",
  mute = true,
  frequency = Skill.Compulsory,
  events = {fk.AfterCardUseDeclared},
  can_trigger = function(self, event, target, player, data)
    return target == player and player:getMark("@@nian_baozhu") > 0 and data.card.trueName == "slash"
  end,
  on_use = function(self, event, target, player, data)
    data.additionalDamage = (data.additionalDamage or 0) + 1
  end,

  refresh_events = {fk.EventPhaseChanging, fk.Death},
  can_refresh = function(self, event, target, player, data)
    return target == player and player.tag["nian_baozhu"] == 1
      and data.from == Player.NotActive
  end,
  on_refresh = function(self, event, target, player, data)
    player.tag["nian_baozhu"] = 0
    for _, p in pairs(player.room.players) do
      if player:getMark("@@nian_baozhu") ~= 0 then
        player.room:removePlayerMark(player, "@@nian_baozhu", 1)
      end
    end
  end,
}
baozhu:addRelatedSkill(baozhu_add)
Fk:addSkill(baozhu)

local yanhua = fk.CreateActiveSkill{
  name = "nian_yanhua",
  anim_type = "special",
  frequency = Skill.Limited,
  can_use = function(self, player)
    return player:usedSkillTimes(self.name, Player.HistoryGame) == 0
  end,
  card_filter = Util.FalseFunc,
  target_filter = function(self, to_select, selected, selected_cards)
    return #selected == 0 and Fk:currentRoom():getPlayerById(to_select):getMark("@@nian_yanhua") == 0
  end,
  on_use = function(self, room, effect)
    local target = room:getPlayerById(effect.tos[1])
    if target.dead then return end
    room:setPlayerMark(target, "@@nian_yanhua", 1)
  end,
}
local yanhua_jugde = fk.CreateTriggerSkill{
  name = "#nian_yanhua_jugde",
  mute = true,
  frequency = Skill.Compulsory,
  events = {fk.DamageCaused, fk.DamageInflicted},
  can_trigger = function(self, event, target, player, data)
    if target == player then
      if event == fk.DamageCaused then
        return target:getMark("@@nian_yanhua") > 0
      else
        return data.to:getMark("@@nian_yanhua") > 0
      end
    end
  end,
  on_use = function(self, event, target, player, data)
    local room = player.room
    local judge = {
      who = player,
      reason = self.name,
      pattern = ".|.|heart,diamond",
    }
    room:judge(judge)
    if judge.card.color == Card.Red then
      data.damage = 0
    end
  end,

  refresh_events = {fk.EventPhaseChanging},
  can_refresh = function(self, event, target, player, data)
    return target == player and player.tag["nian_yanhua"] == 1
      and data.from == Player.NotActive
  end,
  on_refresh = function(self, event, target, player, data)
    player.tag["nian_yanhua"] = 0
    for _, p in pairs(player.room.players) do
      if player:getMark("@@nian_yanhua") ~= 0 then
        player.room:removePlayerMark(player, "@@nian_yanhua", 1)
      end
    end
  end,
}
yanhua:addRelatedSkill(yanhua_jugde)
Fk:addSkill(yanhua)

Fk:loadTranslationTable{
  ["nian_capturing"] = "年兽大作战",
  [":nian_capturing"] = desc_nian_capturing,
  ["nian_intro"] = "爆竹声中一岁除！",
  ["nian_changeSeat_intro"] = "由人类率先发起进攻！",

  ["nian_fulu"] = "福禄",
  [":nian_fulu"] = "锁定技，游戏开始时，你摸两张牌；你的摸牌阶段摸牌数+2。",

  ["nian_buzhuo"] = "捕捉",
  [":nian_buzhuo"] = "出牌阶段限一次，你可以指定一名生肖兽，进行捕捉。有[100-12X]%的概率捕捉成功（X为其体力值）。成功则其死亡，你失去上次以此法获得的技能，然后获得其生肖技能。",

  ["nian_baozhu"] = "爆竹",
  [":nian_baozhu"] = "限定技，出牌阶段，你可以令所有角色各失去1点体力和所有护甲，得到以下效果直到你的下个回合开始：使用的【杀】造成的伤害+1。",
  ["#nian_baozhu_add"] = "爆竹-加伤",
  ["@@nian_baozhu"] = "爆竹",

  ["nian_yanhua"] = "烟花",
  [":nian_yanhua"] = "限定技，出牌阶段，你可以指定一名其他角色，其得到以下效果直到你的下个回合开始：造成或受到伤害时，进行一次判定，若结果为红色，防止此伤害。",
  ["#nian_yanhua_jugde"] = "烟花-判定",
  ["@@nian_yanhua"] = "烟花",
}

return nian_capturing
